package com.hao.array;

/**
 * TODO
 * 压缩数组成为稀疏数组的实现
 * @author 97472
 * @version 1.0
 * @date 2021/4/12 10:26
 */
public class SparseArr {
    public static void main(String[] args) {
        /** 初始化围棋盘
         *  0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0
         *  0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0
         *  0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0
         *  0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0
         *  0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0
         *  0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0
         *  0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0
         *  0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0
         *  0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0
         *  0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0
         *  0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0
         *  0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0
         *  0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0
         *  0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0
         *  0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0
         *  0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0
         *  0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0
         *  0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0
         *  0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0
         */
        int[][] chess = new int[19][19];

//        在三行四列上下一颗黑棋（值为1），四行四列上下一颗白棋（值为2）
        chess[2][3] = 1;
        chess[3][3] = 2;

        // 对数组进行压缩为稀疏数组
        int[][] sparseArr = compression(chess);
        // 打印
        for (int i = 0; i < sparseArr.length; i++) {
            for (int j = 0; j < sparseArr[i].length; j++) {
                System.out.print("  "+sparseArr[i][j]);
            }
            System.out.println();
        }
        System.out.println("---------------------------------");
        // 对稀疏数组进行还原
        chess = restore(sparseArr);
        for (int i = 0; i < chess.length; i++) {
            for (int j = 0; j < chess[i].length; j++) {
                System.out.print("  "+chess[i][j]);
            }
            System.out.println();
        }
    }

    /**
     * 对数组进行压缩
     * @param data
     * @return
     */
    public static int[][] compression(int[][] data){
        // 获取数组中的数据元素的总数
        int count = 0;
        for (int i = 0; i < data.length; i++) {
            for (int j = 0; j < data[i].length; j++) {
                boolean isDown = data[i][j] != 0;
                if (isDown){
                    count++;
                }
            }
        }

        /**
         * 创建稀疏数组
         * 稀疏数组是一个3列，行数与元素数组数据元素总量一致
         * 三列分别保存
         * x y val
          */
        int[][] sparseArr = new int[count][3];
        count = 0;
        // 对原数组进行压缩
        for (int i = 0; i < data.length; i++) {
            for (int j = 0; j < data[i].length; j++) {
                boolean isDown = data[i][j] != 0;
                if (isDown){
                    sparseArr[count][0] = i;
                    sparseArr[count][1] = j;
                    sparseArr[count][2] = data[i][j];
                    count++;
                }
            }
        }
        return sparseArr;
    }

    /**
     * 还原稀疏数组
     * @param sparseArr
     */
    public static int[][] restore(int[][] sparseArr){
        // 创建一个棋盘数组
        int[][] chess = new int[19][19];
        // 解析稀疏数组
        for (int i = 0; i < sparseArr.length; i++) {
            int x = 0;
            int y = 0;
            int value = 0;
            for (int j = 0; j < sparseArr[i].length; j++) {
                switch (j){
                    case 0:
                        x = sparseArr[i][j];
                        break;
                    case 1:
                        y = sparseArr[i][j];
                        break;
                    case 2:
                        value = sparseArr[i][j];
                        break;
                    default:
                        break;
                }
            }
            chess[x][y] = value;
        }
        return chess;
    }
}
